<?php

if( ! defined('DOCROOT') )
{
    require_once '/var/www/advancelab/chilik2/unittest/bootstrap.php';
}

class MvcApplicationTest extends UnitTestCase
{
    
    function testingRequestParser()
    {
        $config = new SimpleApp();
        $requestParser = $config->createRequestParser();
        $this->assertEqual( $requestParser, new TestRequestParser() );
        $this->assertTrue( $requestParser instanceof Abstraction\RequestParser );
    }
    
    function testingNumber1()
    {
        $config = new SimpleApp();
        $app = new Core\MvcApplication( $config );
        
        $this->assertEqual( $config, new SimpleApp() );
        $this->assertTrue( $config instanceof Base\AppConfiguration );
        
        $this->assertEqual( $app, new Core\MvcApplication( $config ) );
        $this->assertTrue( $app instanceof Base\ApplicationBase );
        
        $app->run();
        
        $this->assertEqual( 'BODY: Name: name, Vars: array ([CR])', $config->store ); 
        
        /* $this->dump($app); */
    }
    
    function testingInternalRedirect()
    {
        $config = new SimpleApp();
        $config->router = 'InRedirectController';
        
        $app = new Core\MvcApplication( $config );
        $app->run();
        
        $this->assertTrue( $config instanceof Base\AppConfiguration );
        $this->assertTrue( $app instanceof Base\ApplicationBase );
        
        $this->assertEqual( 'BODY: Name: name, Vars: array ([CR]  \'nonRedirVar\' => 4,[CR]  \'reqRedirVar\' => 4,[CR])', $config->store );
        
        /* $this->dump($app); */
    }
    
    function testingExternalRedirect()
    {
        $config = new SimpleApp();
        $config->router = 'InRedirectController';
        
        $app = new Core\MvcApplication( $config );
        $app->run();
        
        $this->assertTrue( $config instanceof Base\AppConfiguration );
        $this->assertTrue( $app instanceof Base\ApplicationBase );
        
        $this->assertEqual( 'BODY: Name: name, Vars: array ([CR]  \'nonRedirVar\' => 4,[CR]  \'reqRedirVar\' => 4,[CR])', $config->store );
        
        /* $this->dump($app); */
    }
    
    function testingRoutingException()
    {
        $config = new SimpleApp();
        $config->requestParser = 'FaultyRoutes';
        
        $app = new Core\MvcApplication( $config );
        $app->run();
        
        $this->assertTrue( $config instanceof Base\AppConfiguration );
        $this->assertTrue( $app instanceof Base\ApplicationBase );
        
        $this->assertEqual( 'BODY: Name: name, Vars: array ([CR]  \'fatal\' => \'Very Fatal !!!\',[CR])', $config->store );
        /* $this->dump($app); */
    }
    
    function testingInvalidResultObject()
    {
        $config = new SimpleApp();
        $config->router = 'FaultyAction';
        
        $app = new Core\MvcApplication( $config );
        
        $this->assertTrue( $config instanceof Base\AppConfiguration );
        $this->assertTrue( $app instanceof Base\ApplicationBase );
        
        try
        {
            $app->run();
            $this->fail('Expected Exception not thrown');
        }
        catch( \Exception $e )
        {
            $this->assertEqual( 'The action "no-return" of controller "testController2" did not return an Entity\MvcResult object.', $e->getMessage() );
        }
        
        /* $this->dump($app); */
    }
    
    function testingPreRoutingFilters()
    {
        $config = new SimpleApp();
        $config->preRoutingFilters = TRUE;
        
        $app = new Core\MvcApplication( $config );
        $app->run();
        
        $this->assertTrue( $config instanceof Base\AppConfiguration );
        $this->assertTrue( $app instanceof Base\ApplicationBase );
        
        $this->assertEqual( 'BODY: Name: name, Vars: array ([CR]  \'newVars\' => \'Yes, we did pre routing filter !\',[CR])', $config->store );
        
        /* $this->dump($app); */
    }
    
    function testingInternalRedirectRequestFilter()
    {
        $config = new SimpleApp();
        $config->internalRedirectRequestFilter = TRUE;
        
        $app = new Core\MvcApplication( $config );
        $app->run();
        
        $this->assertTrue( $config instanceof Base\AppConfiguration );
        $this->assertTrue( $app instanceof Base\ApplicationBase );
        
        $this->assertEqual( 'BODY: Name: name, Vars: array ([CR]  \'fatal\' => \'Very Fatal !!!\',[CR])', $config->store );
        
        /* $this->dump($app); */
    }
    
    function testingInternalRedirectRequestFilterException()
    {
        $config = new SimpleApp();
        $config->internalRedirectRequestFilter = 'exception';
        
        $app = new Core\MvcApplication( $config );
        try
        {
            $app->run();
            $this->fail('Expected Exception not thrown.');
        }
        catch( Exception $e )
        {
            $this->assertEqual( '10 redirects have occurred. There is a possible infinite redirect loop. ', $e->getMessage() );
        }
        
        $this->assertTrue( $config instanceof Base\AppConfiguration );
        $this->assertTrue( $app instanceof Base\ApplicationBase );
        
        /* $this->dump($app); */
    }
    
    function testingViewException()
    {
        $config = new SimpleApp();
        $config->view = 'ExceptionView';
        
        $app = new Core\MvcApplication( $config );
        $app->run();
        
        $this->assertTrue( $config instanceof Base\AppConfiguration );
        $this->assertTrue( $app instanceof Base\ApplicationBase );
        
        $this->assertEqual( 'BODY: Name: name, Vars: array ([CR]  \'fatal\' => \'Very Fatal !!!\',[CR])', $config->store );
        
        /* $this->dump($app); */
    }
    
    function testingEndlessLoop()
    {
        $config = new SimpleApp();
        $config->router = 'EndlessInRedirect';
        
        $app = new Core\MvcApplication( $config );
        
        try
        {
            $app->run();
            $this->fail('Expected Exception not thrown.');
        }
        catch( Exception $e )
        {
            $this->assertEqual( '10 redirects have occurred. There is a possible infinite redirect loop. ', $e->getMessage() );
        }
        
        $this->assertTrue( $config instanceof Base\AppConfiguration );
        $this->assertTrue( $app instanceof Base\ApplicationBase );
        
        /* $this->dump($app); */
    }
    
    function testingControllerActionException()
    {
        $config = new SimpleApp();
        $config->router = 'ExceptionInAction';
        
        $app = new Core\MvcApplication( $config );
        $app->run();
        
        $this->assertTrue( $config instanceof Base\AppConfiguration );
        $this->assertTrue( $app instanceof Base\ApplicationBase );
        
        $this->assertEqual( 'BODY: Name: name, Vars: array ([CR]  \'fatal\' => \'Very Fatal !!!\',[CR])', $config->store );
        
        /* $this->dump($app); */
    }
    
    function testingFatalInFatal()
    {
        $config = new SimpleApp();
        $config->router = 'FatalInFatal';
        
        $app = new Core\MvcApplication( $config );
        
        try
        {
            $app->run();
            $this->fail('Expected Exception not thrown.');
        }
        catch( Exception $e )
        {
            $this->assertEqual( 'The request "", "/fatal"() results in an infinite fatal error loop !!', $e->getMessage() );
        }
        
        $this->assertTrue( $config instanceof Base\AppConfiguration );
        $this->assertTrue( $app instanceof Base\ApplicationBase );
        
        /* $this->dump($app); */
    }
    
    function testingNoReturnedVariables()
    {
        $config = new SimpleApp();
        $config->controller = 'EmptyResultController';
        
        $app = new Core\MvcApplication( $config );
        $app->run();
        
        $this->assertTrue( $config instanceof Base\AppConfiguration );
        $this->assertTrue( $app instanceof Base\ApplicationBase );
        
        $this->assertEqual( 'BODY: Name: name, Vars: array ([CR])', $config->store );
        
        /* $this->dump($app); */
    }
    
    function testingAllIsWell()
    {
        $config = new TestWrongObjectApp();
        $app = new Core\MvcApplication( $config );
        $app->run();
        
        $this->assertTrue( $config instanceof Base\AppConfiguration );
        $this->assertTrue( $app instanceof Base\ApplicationBase );
        
        $this->assertEqual( 'BODY: Name: name, Vars: array ([CR])', $config->store );
        
        /* $this->dump($app); */
    }
    
    function testingWrongRequestParserClass()
    {
        try
        {
            $app = TestWrongObjectAppRunner::test( 'request-parser' );
            $this->fail('Expected exception was not thrown');
        }
        catch( Exception $e )
        {
            $this->assertEqual( 'The Application Configuration has returned an invalid object for "requestParser", Instance Of Abstraction\RequestParser expected, but instance of class stdClass found !', $e->getMessage() );
        }
    }
    
    function testingWrongRouterClass()
    {
        try
        {
            $app = TestWrongObjectAppRunner::test( 'router' );
            $this->fail('Expected exception was not thrown');
        }
        catch( Exception $e )
        {
            $this->assertEqual( 'The Application Configuration has returned an invalid object for "router", Instance Of Abstraction\Router expected, but instance of class stdClass found !', $e->getMessage() );
        }
    }
    
    function testingWrongViewClass()
    {
        try
        {
            $app = TestWrongObjectAppRunner::test( 'view' );
            $this->fail('Expected exception was not thrown');
        }
        catch( Exception $e )
        {
            $this->assertEqual( 'The Application Configuration has returned an invalid object for "view", Instance Of Abstraction\MvcView expected, but instance of class stdClass found !', $e->getMessage() );
        }
    }
    
    function testingWrongControllerClass()
    {
        try
        {
            $app = TestWrongObjectAppRunner::test( 'controller' );
            $this->fail('Expected exception was not thrown');
        }
        catch( Exception $e )
        {
            $this->assertEqual( 'The Application Configuration has returned an invalid object for "controller", Instance Of Abstraction\MvcController expected, but instance of class stdClass found !', $e->getMessage() );
        }
    }
    
    function testingWrongResponseWriterClass()
    {
        try
        {
            $app = TestWrongObjectAppRunner::test( 'response-writer' );
            $this->fail('Expected exception was not thrown');
        }
        catch( Exception $e )
        {
            $this->assertEqual( 'The Application Configuration has returned an invalid object for "responseWriter", Instance Of Abstraction\ResponseWriter expected, but instance of class stdClass found !', $e->getMessage() );
        }
    }
    
    function testingWrongFatalRedirectClass()
    {
        try
        {
            $app = TestWrongObjectAppRunner::test( 'fatal' );
            $this->fail('Expected exception was not thrown');
        }
        catch( Exception $e )
        {
            $this->assertEqual( 'The Application Configuration has returned an invalid object for "request", Instance Of Core\MVCRequest expected, but instance of class stdClass found !', $e->getMessage() );
        }
    }
    
}


